<?php

namespace Kiri\Server\Processes;

use Exception;
use Kiri;
use Swoole\Process;

trait TraitProcess
{

    /**
     * @var array
     */
    private array $_process = [];


    /**
     * @param string|array|AbstractProcess $class
     * @return void
     * @throws
     */
    public function addProcess(string|array|AbstractProcess $class): void
    {
        if (!is_array($class)) $class = [$class];
        foreach ($class as $name) {
            if (is_string($name)) $name = Kiri::getDi()->get($name);
            if (isset($this->_process[$name->getName()])) {
                throw new Exception('AbstractProcess(' . $name->getName() . ') is exists.');
            }
            $this->_process[$name->getName()] = $this->genProcess($name);
        }
    }


    /**
     * @param AbstractProcess $name
     * @return Process
     */
    private function genProcess(AbstractProcess $name): Process
    {
        return new Process(function (Process $process) use ($name) {
            $process->name('[' . \config('id', 'system-service') . '].' . $name->getName() . '[' . $process->pid . ']');
            $name->onShutdown($process)->process($process);
        },
            $name->getRedirectStdinAndStdout(),
            $name->getPipeType(),
            $name->isEnableCoroutine());
    }


    /**
     * @param string $name
     * @return AbstractProcess|null
     */
    public function getProcess(string $name): ?Process
    {
        return $this->_process[$name] ?? null;
    }


    /**
     * @return array
     */
    public function getProcesses(): array
    {
        return $this->_process;
    }
}